const { generateApi } = require('swagger-typescript-api');
const axios = require('axios');
const fs = require('fs');
const path = require('path');
const { TransitionFolder, ConfigName } = require('../utils/Constant')

const swaggerToApi = async (option = {}) => {
    const toApi = async (/** @type {{ swagger: string;input?:string; url?: string; name: any; options:object|undefined }} */ item) => {
        const objParams = {}
        if (item.url) {
            // if (item.swagger === '3.0') {
            //     objParams.url = item.url
            // } else {
                const instance = axios.create();
                const data = await instance.get(item.url);
                objParams.spec = data.data
            // }
        }
        if (!item.url && item.input) {
            objParams.input = path.resolve(option.workspaceFolder, item.input);
        }

        if (!item.url && !item.input) {
            return
        }

        const outputDir = path.resolve(option.workspaceFolder, `./src/api/${item.name}`);
        const baseUrl = item.url?.split('/swagger/')[0] ?? '';
        await generateApi({
            name: item.name,
            output: outputDir,
            modular: true,
            templates: option.templatesPath,
            httpClientType: "axios", // or "fetch"
            generateRouteTypes: true,
            hooks: {
                onPrepareConfig: (currentConfiguration) => {
                    currentConfiguration.apiConfig.baseUrl = baseUrl
                }
            },
            codeGenConstructs: (struct) => ({
                Keyword: {
                    Number: "number",
                    String: "string",
                    Boolean: "boolean",
                    Any: "any",
                    Void: "void",
                    Unknown: "unknown",
                    Null: "null",
                    Undefined: "undefined",
                    Object: "any",
                    File: "File",
                    Date: "Date",
                    Type: "type",
                    Enum: "enum",
                    Interface: "interface",
                    Array: "Array",
                    Record: "Record",
                    Intersection: "&",
                    Union: "|",
                },
            }),
            ...objParams,
            ...(option.baseOptions ?? {}),
            ...(item.options ?? {})
        })
        const indexPath = path.resolve(outputDir, 'index.ts')
        fs.access(indexPath, (err) => {
            if (!err) {
                console.error('myfile already exists');
                return;
            }
            const content =
                `import { Api } from "./Api";
//import AddInterceptor from "../AxiosInterceptor"
const api = new Api({baseURL:"${baseUrl}"})
//AddInterceptor(api.instance)
export default api`
            fs.appendFile(indexPath, content, (err) => {
                if (err) throw err;
                console.log('The file has been saved!');
            })
        })
    }
    if (option.swaggerUrls) {
        for (let i = 0; i < option.swaggerUrls.length; i++) {
            await toApi(option.swaggerUrls[i]);
        }
    }
}

const copyTemplates = (/** @type {string} */targetPath) => {
    const templatesPath = path.resolve(__dirname, './templates')
    const targetFullPath = path.resolve(targetPath, `./${TransitionFolder}`)
    fs.cpSync(templatesPath, targetFullPath, { recursive: true })
}

const copyConfigFile = (/** @type {string} */targetPath) => {
    const configPath = path.resolve(__dirname, `../utils/${ConfigName}.cjs`)
    const targetFullPath = path.resolve(targetPath, `./${ConfigName}.cjs`)
    fs.copyFileSync(configPath, targetFullPath)
}

module.exports = { swaggerToApi, copyTemplates, copyConfigFile };